
/**
  ******************************************************************************
  * Copyright 2021 The Microbee Authors. All Rights Reserved.
  * 
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
  * You may obtain a copy of the License at
  * 
  * http://www.apache.org/licenses/LICENSE-2.0
  * 
  * Unless required by applicable law or agreed to in writing, software
  * distributed under the License is distributed on an "AS IS" BASIS,
  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  * See the License for the specific language governing permissions and
  * limitations under the License.
  * 
  * @file       mb_landing.h
  * @author     baiyang
  * @date       2023-7-13
  ******************************************************************************
  */

#pragma once

#ifdef __cplusplus
extern "C"{
#endif

/*----------------------------------include-----------------------------------*/
#include <stdbool.h>

#include <vehicle/mb_fixed_wing.h>
/*-----------------------------------macro------------------------------------*/

/*----------------------------------typedef-----------------------------------*/
// NOTE: make sure to update is_type_valid()
enum Landing_Type {
    LANDING_TYPE_STANDARD_GLIDE_SLOPE = 0,
#if HAL_LANDING_DEEPSTALL_ENABLED
    LANDING_TYPE_DEEPSTALL = 1,
#endif
//      TODO: TYPE_PARACHUTE,
//      TODO: TYPE_HELICAL,
};

// we support upto 32 boolean bits for users wanting to change landing behaviour.
enum LandingOptionsMask {
    LOM_ON_LANDING_FLARE_USE_THR_MIN                   = (1<<0),   // If set then set trottle to thr_min instead of zero on final flare
    LOM_ON_LANDING_USE_ARSPD_MAX                       = (1<<1),   // If set then allow landing throttle constraint to be increased from trim airspeed to max airspeed (ARSPD_FBW_MAX)
};

enum LandingSlopeStage  {
    LDSS_NORMAL = 0,
    LDSS_APPROACH = 1,
    LDSS_PREFLARE = 2,
    LDSS_FINAL = 3,
};

typedef struct mb_landing *mb_landing_t;
typedef const struct mb_landing *mb_landing_const_t;

// command structure
struct mb_landing {
    struct {
        // denotes if a go-around has been commanded for landing
        bool commanded_go_around:1;

        // are we in auto and flight_stage is LAND
        bool in_progress:1;
    } flags;

    Param_int16 _options;    // user-configurable bitmask options, via a parameter, for landing

    // same as land_slope but sampled once before a rangefinder changes the slope. This should be the original mission planned slope
    float initial_slope;

    // calculated approach slope during auto-landing: ((prev_WP_loc.alt - next_WP_loc.alt)*0.01f - flare_sec * sink_rate) / prev_WP_loc.get_distance(next_WP_loc)
    float slope;

    float height_flare_log;

#if 0
    AP_Mission &mission;
    AP_AHRS &ahrs;
    AP_TECS *tecs_Controller;
    AP_Navigation *nav_controller;
#endif

    mb_fixed_wing_t aparm;

#if HAL_LANDING_DEEPSTALL_ENABLED
    // support for deepstall landings
    AP_Landing_Deepstall deepstall;
#endif

    Param_int16 pitch_cd;
    Param_float flare_alt;
    Param_float flare_sec;
    Param_float pre_flare_airspeed;
    Param_float pre_flare_alt;
    Param_float pre_flare_sec;
    Param_float slope_recalc_shallow_threshold;
    Param_float slope_recalc_steep_threshold_to_abort;
    Param_int8 disarm_delay;
    Param_int8 then_servos_neutral;
    Param_int8 abort_throttle_enable;
    Param_int8 flap_percent;
    Param_int8 throttle_slewrate;
    Param_int8 type;
    Param_int8 flare_effectivness_pct;
    Param_float wind_comp;

    // Land Type STANDARD GLIDE SLOPE

    enum LandingSlopeStage type_slope_stage;

    struct {
        // once landed, post some landing statistics to the GCS
        bool post_stats:1;

        bool has_aborted_due_to_slope_recalc:1;
    } type_slope_flags;
};
/*----------------------------------variable----------------------------------*/

/*-------------------------------------os-------------------------------------*/

/*----------------------------------function----------------------------------*/
bool landing_is_flaring(void);
bool landing_is_on_approach(void);
bool landing_is_ground_steering_allowed(void);
bool landing_type_slope_is_flaring(void);
bool landing_type_slope_is_on_approach(void);
bool landing_type_slope_is_expecting_impact(void);
bool landing_type_slope_is_complete(void);
bool landing_is_expecting_impact(void);
bool landing_override_servos(void);
int16_t landing_get_pitch_cd(void);
float landing_get_flare_sec(void);
int8_t landing_get_disarm_delay(void);
int8_t landing_get_then_servos_neutral(void);
int8_t landing_get_abort_throttle_enable(void);
int8_t landing_get_flap_percent(void);
int8_t landing_get_throttle_slewrate(void);
bool landing_is_commanded_go_around(void);
void landing_set_initial_slope(void);
/*------------------------------------test------------------------------------*/

#ifdef __cplusplus
}
#endif



